import asyncio
import logging

from openpyxl.workbook import Workbook

from crawler.page.base_page import BaseCrawlerPage

LOGGER = logging.getLogger(__name__)


class SMSPage(BaseCrawlerPage):
    # 菜单栏选择器
    menu_selector = 'xpath=//*[@id="app"]/section/main/section/aside/div/ul'
    # 通用查询菜单选择器
    common_query_selector = f'{menu_selector}//*[@class="ant-menu-submenu-title"][.//*[text()="通用查询"]]'
    # 通用查询菜单判断是否展开属性 true 展开 false 未展开
    aria_expanded = 'aria-expanded'
    # 短信发送明细页面选择器
    sms_send_detail_selector = f'{menu_selector}//*[text()="短信发送明细"]'
    # 通用查询菜单判断是否展开属性 true 展开 false 未展开
    # 页面搜索框选择器
    # 创建时间-日期开始
    create_time_start_selector = 'xpath=//*[@id="query_submitSendTime"]'
    # 创建时间-日期结束
    create_time_end_selector = 'xpath=//*[@id="waterCanves"]/div[1]/div/form/div/div[7]/div/div[2]/div/div/div/div[3]/input'
    # 发送策略-下拉框
    send_strategy_selector = 'xpath=//*[@id="query_strategy"]'
    # 处理状态-下拉框
    handle_status_selector = 'xpath=//*[@id="query_status"]'
    # 搜索按钮选择器
    search_button_selector = 'xpath=//*[@id="waterCanves"]/div[1]/div/form/div/div[12]/button[1]'
    # 表格数据选择器
    table_selector = '.ag-center-cols-container'
    # 下一页按钮选择器
    next_button_selector = '.ant-pagination-next > .ant-pagination-item-link'

    columns = {
        '系统提交发送时间': 'submitSendTime',
        '案件编号': 'sysRecordkey',
        '客户姓名': 'custName',
        '客户手机号': 'mobile',
        '模板编号': 'modelCode',
        '处理状态': 'status',
        '发送机构组': 'companyNoText',
        '发送人员': 'userName'
    }

    async def data_write_excel(self, search, file_path):
        """
        短信页面数据写入 Excel 文件

        :param file_path: 数据保存文件路径
        :param search: 搜索参数
        :return: 分页表格数据
        """
        # 数据写入
        # 创建一个新的工作簿
        wb = Workbook()
        # 获取活动工作表
        ws = wb.active

        start_date = search.get("start_date")
        end_date = search.get("end_date")
        send_strategy = search.get("send_strategy")
        status = search.get("status")
        if not start_date and not end_date and not send_strategy and not status:
            LOGGER.error("查询参数有误,无法查询")
            raise ValueError("查询参数有误,无法查询")
        if not status:
            status = []
        else:
            status = status.split(",")

        LOGGER.info("入参: start_date=%s, end_date=%s, send_strategy=%s, status=%s", start_date, end_date,
                    send_strategy, status)
        title_data = list(self.columns.keys())
        ws.append(title_data)
        self._save_workbook(wb, file_path)

        try:
            LOGGER.info("开始获取短信页面数据")
            menu_element = await self._get_element(self.menu_selector, "菜单栏")
            if menu_element:
                common_query_element = await self._get_element(self.common_query_selector, "通用查询菜单")
                if common_query_element:
                    await self._expand_menu(common_query_element, self.aria_expanded)
                    await asyncio.sleep(0.3)
                    sms_send_detail_element = await self._get_element(self.sms_send_detail_selector, "短信发送明细页面")
                    if sms_send_detail_element:
                        await self._click_element(sms_send_detail_element, "短信发送明细页面")
                        await self._set_date_range(start_date, end_date)
                        await self._set_handle_status(status)
                        await self._set_send_strategy(send_strategy)
                        await self._click_search_button(self.search_button_selector)
                        await self._parse_table_data(ws, file_path, wb, self.columns)
        except Exception as e:
            # 抛出
            LOGGER.error("获取短信页面数据时出错: %s", str(e), exc_info=True)
            raise
        finally:
            self._save_workbook(wb, file_path)
            await self.page.reload()

    async def _set_handle_status(self, status):
        """设置处理状态并记录日志"""
        if status and len(status) > 0:
            for i in range(len(status)):
                LOGGER.info("给处理状态-下拉框赋值-值%d", i + 1)
                try:
                    await self.page.type(self.handle_status_selector, status[i])
                    await self.page.keyboard.press("Enter")
                    await asyncio.sleep(0.2)
                    LOGGER.info("已给处理状态-下拉框赋值-值%d", i + 1)
                except Exception as e:
                    LOGGER.error("给处理状态-下拉框赋值-值%d 时出错: %s", i + 1, str(e))
                    raise

    async def _set_send_strategy(self, send_strategy):
        """设置发送策略并记录日志"""
        await self.page.fill(self.send_strategy_selector, "")
        if send_strategy:
            LOGGER.info("给发送策略-下拉框赋值")
            try:
                await self.page.type(self.send_strategy_selector, send_strategy)
                await self.page.keyboard.press("Enter")
                LOGGER.info("已给发送策略-下拉框赋值")
            except Exception as e:
                LOGGER.error("给发送策略-下拉框赋值时出错: %s", str(e))
                raise
